package com.violet.rabbitmq.config;

import org.springframework.amqp.core.AcknowledgeMode;
import org.springframework.amqp.rabbit.config.SimpleRabbitListenerContainerFactory;
import org.springframework.amqp.rabbit.connection.CachingConnectionFactory;
import org.springframework.amqp.rabbit.connection.ConnectionFactory;
import org.springframework.amqp.rabbit.core.RabbitAdmin;
import org.springframework.amqp.rabbit.core.RabbitTemplate;
import org.springframework.amqp.support.converter.Jackson2JsonMessageConverter;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.autoconfigure.amqp.SimpleRabbitListenerContainerFactoryConfigurer;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Primary;
import org.springframework.stereotype.Component;

/**
 * @Author: wqf
 * @Date: 2024/03/14
 * @Description: 主rabbitmq配置
 */
@Component
@Configuration
public class PrimaryRabbitMqConfig {

    //主mq配置 相关bean名称常量
    public static final String PRIMARY_FACTORY = "primaryConnectionFactory";
    //设备云mq配置 相关bean名称常量
    public static final String PRIMARY_LISTENER = "primaryListener";
    public static final String PRIMARY_TEMPLATE = "primaryTemplate";
    public static final String PRIMARY_RABBIT_ADMIN = "primaryRabbitAdmin";

    /**
     * 主mq连接配置
     */
    @Bean(name = PRIMARY_FACTORY)
    @Primary
    public ConnectionFactory connectionFactory(
            @Value("${spring.rabbitmq.host}") String host,
            @Value("${spring.rabbitmq.port}") int port,
            @Value("${spring.rabbitmq.username}") String username,
            @Value("${spring.rabbitmq.password}") String password,
            @Value("${spring.rabbitmq.virtual-host}") String virtualHost
    ) {
        CachingConnectionFactory connectionFactory = new CachingConnectionFactory();

        connectionFactory.setHost(host);
        connectionFactory.setPort(port);
        connectionFactory.setUsername(username);
        connectionFactory.setPassword(password);
        connectionFactory.setVirtualHost(virtualHost);
        //消息发布成功回调确认
        connectionFactory.setPublisherReturns(true);
        //消息成功发送回调确认
        connectionFactory.setPublisherConfirmType(CachingConnectionFactory.ConfirmType.CORRELATED);
        return connectionFactory;
    }

    @Bean(PRIMARY_LISTENER)
    public SimpleRabbitListenerContainerFactory listenerContainerFactory(
            SimpleRabbitListenerContainerFactoryConfigurer configurer,
            @Qualifier(PRIMARY_FACTORY) ConnectionFactory connectionFactory
    ) {
        SimpleRabbitListenerContainerFactory factory = new SimpleRabbitListenerContainerFactory();
        //设置手动ack模式 要和yml配置保持一致，不然会覆盖yml文件的配置
        factory.setAcknowledgeMode(AcknowledgeMode.MANUAL);
        factory.setConnectionFactory(connectionFactory);
        factory.setMessageConverter(new Jackson2JsonMessageConverter());
        configurer.configure(factory, connectionFactory);
        return factory;
    }

    @Bean(PRIMARY_TEMPLATE)
    public RabbitTemplate rabbitTemplate(
            @Qualifier(PRIMARY_FACTORY) ConnectionFactory connectionFactory
    ) {

        RabbitTemplate rabbitTemplate = new RabbitTemplate(connectionFactory);
        rabbitTemplate.setMandatory(true);
        rabbitTemplate.setMessageConverter(new Jackson2JsonMessageConverter());
        return rabbitTemplate;
    }

    /**
     * 创建RabbitAdmin bean
     */
    @Bean(PRIMARY_RABBIT_ADMIN)
    public RabbitAdmin rabbitAdmin(@Qualifier(PRIMARY_FACTORY) ConnectionFactory connectionFactory) {
        return new RabbitAdmin(connectionFactory);
    }
}
